# 表格
import tkinter as tk
from tkinter import Scrollbar
from tkinter.ttk import Treeview
from tkinter import ttk
from tools import *
from tab_header import *
from tab_grid import *
from sys_input_box import *
from sys_sqlite3 import *
from sys_config import *
# from babel.numbers import 
from datetime import datetime
from tab_func import *

"""查询页面
"""
class TabQuery():
    #初始化：容器、列定义
    """初始化
    parent      父窗口
    ctrl        业务控制器，要求有 conf 方法，以取得配置；以及方法:add,delete,edit,output,input,print,custom1,custom2...，这些方法要接收tab_grid参数
    buttons:    右侧按钮定义（逗号分隔的字符串）:add,delete,edit,output,input,print
    operation:  其他操作方法定义（逗号分隔的字符串），如:重算,合并，分别对应ctrl的 custom1,custom2 方法
    init_size:  窗口初始大小: 0=小，1=中，9=最大化
    """
    def __init__(self, parent, ctrl, buttons = '', operation = '', init_size = 0):
        self.parent  = parent
        self.ctrl    = ctrl
        self.buttons   = buttons
        self.operation = operation
        self.tools   = Tools()
        self.sys_sqlite   = SysSqlite()
        self.tab_func      = TabFunc()
        self.conf   = self.ctrl.conf()
        # if self.__check() == False: return
        self.conf = self.tab_func.check_query(self.conf)
        if self.conf == False: return

        self.config = SysConfig()
        self.config.init()        
        
        self.where_exp = '' # 当前查询条件
        self.order_exp = '' # 当前排序
        self.ctrl_method_caption = {
            'add':      '添加',
            'delete':   '删除',
            'edit':     '编辑',
            'output':   '导出',
            'input':    '导入',
            'print':    '打印'
        }

        self.window = tk.Toplevel(parent)
        self.window.title(self.conf['title'])
        self.window.transient(parent)  # 设置为模态，不设置此项时调用tools.msg会导致后面的窗口显示出来

        if init_size == 0:
            self.window.geometry(self.tools.get_geometry(parent, 600, 336))
        if init_size == 1:
            self.window.geometry(self.tools.get_geometry(parent, 1000, 560))
        else:
            self.window.geometry(self.tools.get_geometry(parent, 1600, 896))
            
        self.window.minsize(width=600, height=336)  # 设置最小尺寸
        # self.window.maxsize(width=self.window.winfo_screenwidth(), height=self.window.winfo_screenheight())  # 设置最大尺寸（根据屏幕分辨率调整）

        if init_size == 9:  self.window.wm_state('zoomed') #最大化
        self.window.resizable(True, True)
        
        # 绑定窗口变事件
        self.window.bind("<Configure>", self.on_window_configure)  
        self.window.bind("<Visibility>", self.on_window_configure) 
        self.window.bind("<Alt-q>", self.on_window_alt_key_q)
        self.window.bind("<Alt-c>", self.on_window_alt_key_c)

        self.window.grab_set()        # 阻止用户与主窗口交互
        self.__gen_ui()

    def __gen_ui(self):
        """生成用户界面：查询条件、搜索、表头、表格、右侧按钮
        """
        font_size = self.config.value('ui', 'font_size', 12)

        # 查询条件
        self.frameWhere = Frame(self.window, bg='blue')
        self.frameWhere.place(x=5, y=5, width=1000, height=30, bordermode='inside')

        # 搜索
        self.frameSearch = Frame(self.window, bg='green')
        self.frameSearch.place(x=5, y=35, width=1000, height=30, bordermode='inside')

        self.stat_str = StringVar()
        search_lbl  = Label(self.frameSearch, width=20, height=1, anchor='w', border=0, textvariable = self.stat_str, font=('宋体', font_size))
        search_lbl.pack(side='left')

        search_button = Button(self.frameSearch, text="搜索", width=5, height=1, command=self.search_str, font=('宋体', font_size))
        search_button.pack(side='right')
        search_button = Button(self.frameSearch, text="统计", width=5, height=1, command=self.tab_stat)
        search_button.pack(side='right')
        search_button = Button(self.frameSearch, text="删除选中行", width=10, height=1, command=self.tab_delete2)
        search_button.pack(side='right')
        search_button = Button(self.frameSearch, text="删除指定行", width=10, height=1, command=self.tab_delete)
        search_button.pack(side='right')

        self.search_entry = Entry(self.frameSearch, width=20)
        self.search_entry.pack(side='right', padx=10 )

        #使用 TabHeader 组件实现表头
        self.frameHeader = Frame(self.window, bg='#666')
        self.frameHeader.place(x=5, y=65, width=1000, height=30, bordermode='inside')
        self.th = TabHeader(self.frameHeader, self.conf['header'], self.onTabHeaderClick)

        # 结果数据
        self.frameData = Frame(self.window, borderwidth=2)
        self.frameData.place(x=3, y=95, width=1000, height=300, bordermode='inside')
        self.tg = TabGrid(self.frameData, self.conf)

        #右侧按钮 , command =  lambda event: onButonClick('query')
        self.frameRight = Frame(self.window)
        self.frameRight.place(x=1, y=5, width=100, height=300, bordermode='inside')

        _button_width = 10
        btn_query = Button(self.frameRight, text = self.conf.get('query_caption', '查询'),  width=_button_width, height=1, command = lambda : self.onButonClick('query'), font=('宋体', font_size))
        btn_query.pack(side='top', anchor='center', padx=1, pady=1)

        print("__gen_ui", self.buttons)
        if len(self.buttons) > 0:
            buttons_arr = self.buttons.split(',')
            # if self.tools.in_list(buttons_arr, 'add'):
            #     print("__gen_ui", '添加')
            #     btn = Button(self.frameRight, text ="添加", width=_button_width, height=1, command = lambda: self.onCtrlButonClick('add')).pack(side='top', anchor='center', padx=1, pady=1)
            # if self.tools.in_list(buttons_arr, 'delete'):
            #     btn = Button(self.frameRight, text ="删除", width=_button_width, height=1, command = lambda: self.onCtrlButonClick('delete')).pack(side='top', anchor='center', padx=1, pady=1)
            i = 0
            for item in buttons_arr:
                _caption = self.ctrl_method_caption.get(item, False)
                if _caption == False:
                    print("__gen_ui", f"业务控制器方法【{item}】无效，不能生成按钮")
                else:
                    _y = 10 if i == 0 else 1
                    print("__gen_ui", i, _y)
                    btn = Button(self.frameRight, 
                                 text=_caption, 
                                 width=_button_width, 
                                 height=1, 
                                 command = lambda: self.onCtrlButonClick(item),
                                 font=('宋体', font_size)).pack(side='top', anchor='center', padx=1, pady=_y)
                                 
                    i += 1

        btn_close = Button(self.frameRight, 
                           text ="关闭", 
                           width=_button_width, 
                           height=1, 
                           command = lambda : self.onButonClick('close'), 
                           font=('宋体', font_size)).pack(side='top', anchor='center', padx=1, pady=10)

        btn_query.focus()

    def onTabHeaderClick(self, order_exp):
        print("onTabHeaderClick", order_exp)
        self.order_exp = order_exp
        self.do_query()

    # 右侧按钮事件
    def onButonClick(self, exp):
        print("onButonClick", exp)
        if exp == 'close':
            self.window.destroy()
        if exp == 'query':
            self.do_query()
    # 右侧业务控制器按钮事件
    def onCtrlButonClick(self, func = '', operation = ''):
        try:
           if len(func) > 0: getattr(self.ctrl, func)(self.tg) 
        except AttributeError as e:
            print(f"onCtrlButonClick Error: {e};")
            self.tools.msg(f"发生错误:{e}", 'error')

    def on_window_configure(self, event):
        self.window_adjust()

    # 键盘事件
    def on_window_alt_key_q(self, event):
        print("on_window_alt_key_q:")
        self.tg.create_tab(self.th.get_char_width())
        
    def on_window_alt_key_c(self, event):
        print("on_window_alt_key_c:")
        self.window.destroy()

    # 搜索
    def search_str(self):
        ss = self.search_entry.get()
        if len(ss) == 0:
            # messagebox.showwarning("警告", "请输入搜索内容！")
            self.tools.msg('请输入搜索内容！', 'warning')
            return
        
        # ret = self.tools.msg('请输入搜索内容！', 'yesno')
        # self.tools.msg('hi')
        print("search_str", ss, self.tg.search(ss))

    def tab_stat(self):
        _count = self.tg.get_count()
        selected_count = self.tg.get_selected_count()
        print(f"tab_stat,行数{_count}：选中{selected_count}行")
        self.stat_str.set(f"行数{_count},选中{selected_count}行")

        selected_num = self.tg.get_selected_num()
        print("selected_num", selected_num)
        selected_id = self.tg.get_selected_id()
        print("selected_id", selected_id)
        get_cell = self.tg.get_cell(5, 3)
        print("get_cell", get_cell)
        SysInputBox(self.window, self.str_test, '请输入:', 'str')

    def str_test(self, s):
        # str1 = self.tools.sub_str(s, 8, 5)
        # str1 = self.tools.wrap_text_gbk(s, 5)
        # print(f"str_test,s:{s},str1:{str1}")
        # formatted_num = format_decimal(123456.789, format="#,##0.00")
        formatted_num =  "{:,.0f}".format(float(s))
        print(formatted_num)  # 输出：123,456.79
      
        date_string = "2021-01-01 12:30:45"
        format_string = "%Y-%m-%d %H:%M:%S"
        date_time = datetime.strptime(date_string, format_string)
        print(date_time)

    # 删除指定行
    def tab_delete(self):
        SysInputBox(self.window, self.tab_delete_do, '请输入行号:', 'number', True, 1)

    def tab_delete_do(self, content):
        print("tab_delete_do", content)
        if content == '': return
        if content.isdigit() == False: return
        self.tg.delete(int(content))
    # 删除选中行
    def tab_delete2(self):
        self.tg.delete2()

    # 根据窗口大小调整内部组件的位置和大小
    def window_adjust(self):
        # 获取宽度和高度
        win_width   = self.window.winfo_width()
        win_height  = self.window.winfo_height()
        # print(f"screen:{win_width},{win_height}")
        _right  = 100
        _left   = win_width - _right
        if _left < 1:
            return
        
        self.frameWhere.place(x=5, y=5, width=_left, height=30) 
        self.frameSearch.place(x=5, y=35, width=_left-4, height=30) 
        self.frameHeader.place(x=5, y=65, width=_left, height=30) 
        self.frameData.place(x=5, y=95, width=_left-4, height=(win_height - 99)) 
        self.frameRight.place(x=_left, y=5, height=win_height)

    # 执行查询            
    def do_query(self):
        # print("onButonClick get_char_width", self.th.get_char_width())
        # self.tg.demo_data(self.th.get_width_list())
        # ret = self.sys_sqlite.query(self.conf['sql'])
        ret = self.ctrl.query('', self.order_exp)
        self.tg.set_data(ret, self.th.get_width_list())
        pass